package com.u.social.multimedia.service.impl;

import com.alibaba.fastjson.JSON;
import com.u.social.multimedia.model.VideoMeta;
import com.u.social.multimedia.service.IVideoService;
import jakarta.json.Json;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.FileSystemResource;
import org.springframework.core.io.Resource;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.util.UUID;

/**
 * @program: u-social
 * @description: 视频逻辑类
 * @author: Alex Wu
 * @createDate: 2025-03-14 11:38
 **/
public class VideoServiceImpl implements IVideoService {
    // 你可以自定义保存文件的目录
    private static final String VIDEO_STORAGE_PATH = "/path/to/storage/directory";


    @Autowired
    private RocketMQTemplate rocketMQTemplate;

    @Autowired
    private RedisTemplate redisTemplate;


    // 处理视频文件上传
    @Override
    public Boolean submitVideo(MultipartFile file, VideoMeta videoMeta) {
        try {
            // 获取上传的文件名
            String fileName = file.getOriginalFilename();
            if (fileName == null) {
                throw new IllegalArgumentException("文件名为空");
            }
            // 保存文件到指定的目录
            File dest = new File(VIDEO_STORAGE_PATH + "/" + fileName);
            file.transferTo(dest);  // 将文件保存到目标路径

            if (!dest.exists()) {
                throw new IllegalArgumentException("文件不存在");
            }

            String metaJson = JSON.toJSONString(videoMeta);

            // 缓存视频元数据到 Redis
            redisTemplate.opsForValue().set("shortvideo:"+ videoMeta.getId(), metaJson);
            rocketMQTemplate.convertAndSend("short-video-topic", metaJson);

            return true;
        } catch (IOException e) {
            // 处理文件上传错误
            e.printStackTrace();
            return false;
        }
    }

    private static final String DASH_OUTPUT_PATH = "/path/to/dash/output"; // DASH 输出路径

    // 处理视频上传并生成 DASH 格式
    public String processAndUploadVideo(VideoMeta videoMeta) throws Exception {
        // 使用 FFmpeg 转码并生成 DASH 分片
        String videoId = UUID.randomUUID().toString(); // 生成视频唯一 ID
        String dashDirectory = DASH_OUTPUT_PATH + "/" + videoId;

        // 创建输出目录
        File outputDir = new File(dashDirectory);
        if (!outputDir.exists()) {
            outputDir.mkdirs();
        }

        // FFmpeg 转码命令
        String ffmpegCommand = String.format("ffmpeg -i %s -map 0 -map 0 -c:v libx264 -preset fast -b:v 800k -maxrate 800k -bufsize 1600k -c:a aac -b:a 128k -ar 44100 -ac 2 -f dash -dash_segment_filename %s/%%03d.m4s %s/manifest.mpd",
                videoMeta.getPath(), dashDirectory, dashDirectory);

        // 执行命令行 FFmpeg 转码
        Process process = Runtime.getRuntime().exec(ffmpegCommand);
        int resultCode = process.waitFor();

        if (resultCode != 0) {
            throw new Exception("FFmpeg 转码失败");
        }
        // 返回生成的视频 ID
        return videoId;
    }

    @Override
    public ResponseEntity<Resource> getVideoManifest(String videoId) {

        try {
            // 获取视频的 manifest.mpd 文件路径
            File mpdFile = new File(DASH_OUTPUT_PATH + "/" + videoId + "/manifest.mpd");

            // 判断文件是否存在
            if (!mpdFile.exists()) {
                return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
            }

            // 将文件转换为 Spring 的 Resource 类型
            Resource resource = new FileSystemResource(mpdFile);

            // 返回文件内容作为响应
            return ResponseEntity.ok()
                    .contentType(MediaType.parseMediaType("application/dash+xml"))
                    .body(resource);
        } catch (Exception e) {
            e.printStackTrace();
            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR)
                    .body(null);
        }
    }

    @Override
    public ResponseEntity<Resource> getVideoSegment(String videoId, String segmentId) {
        try {
            // 获取分片文件路径
            File segmentFile = new File(DASH_OUTPUT_PATH + "/" + videoId + "/" + segmentId);

            // 判断文件是否存在
            if (!segmentFile.exists()) {
                return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
            }
            // 将文件转换为 Spring 的 Resource 类型
            Resource resource = new FileSystemResource(segmentFile);
            // 返回分片文件内容
            return ResponseEntity.ok()
                    .contentType(MediaType.parseMediaType("video/mp4"))
                    .body(resource);
        } catch (Exception e) {
            e.printStackTrace();
            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR)
                    .body(null);
        }
    }

}